// VisaAttributeExplorer.cpp : implementation file
//

#include "stdafx.h"
#include "visaapidemo.h"

#include "VisaAttributeMetadata.h"
#include "VisaAttributeExplorer.h"
#include "VisaApiDemoDlg.h"


#ifdef _DEBUG
#define new DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif


/////////////////////////////////////////////////////////////////////////////
// CVisaAttributeExplorer dialog


CVisaAttributeExplorer::CVisaAttributeExplorer(CVisaApiDemoDlg* pParent)
	: CDialog(CVisaAttributeExplorer::IDD, pParent),
	m_pobjParentDlg(pParent),
	m_ptblCurrAttr(g_tableVisaAttribMetadata)
{
	//{{AFX_DATA_INIT(CVisaAttributeExplorer)
	m_strCurrValue = _T("");
	m_strNewValue = _T("");
	m_iFalse = -1;
	//}}AFX_DATA_INIT
}


BOOL
CVisaAttributeExplorer::Create()
{
	return CDialog::Create(IDD, m_pobjParentDlg);
}


void
CVisaAttributeExplorer::RestoreDialog()
{
	WINDOWPLACEMENT wp;
	wp.length = sizeof(WINDOWPLACEMENT);
	GetWindowPlacement(&wp);
	if (wp.showCmd == SW_SHOWMINIMIZED)
	{
		wp.showCmd = SW_RESTORE;
		SetWindowPlacement(&wp);
	}
	else
	{
		SetActiveWindow();
	}
}


void CVisaAttributeExplorer::DoDataExchange(CDataExchange* pDX)
{
	CDialog::DoDataExchange(pDX);
	//{{AFX_DATA_MAP(CVisaAttributeExplorer)
	DDX_Control(pDX, IDC_VI_TRUE_VALUE, m_btnTrueValue);
	DDX_Control(pDX, IDC_VI_FALSE_VALUE, m_btnFalseValue);
	DDX_Control(pDX, IDC_VI_NEW_VALUE, m_editNewValue);
	DDX_Control(pDX, IDC_VI_DATA_TYPE, m_lblDataType);
	DDX_Control(pDX, IDC_VI_BOOLEAN, m_lblViBoolean);
	DDX_Control(pDX, IDC_SET_ATTRIBUTE, m_btnSetAttribute);
	DDX_Control(pDX, IDC_ATTR_SCOPE, m_lblAttrScope);
	DDX_Control(pDX, IDC_ATTR_ACCESS, m_lblAttrAccess);
	DDX_Control(pDX, IDC_ATTRIBUTE_LIST, m_comboAttributes);
	DDX_Text(pDX, IDC_CURRENT_VALUE, m_strCurrValue);
	DDX_Text(pDX, IDC_VI_NEW_VALUE, m_strNewValue);
	DDX_Radio(pDX, IDC_VI_FALSE_VALUE, m_iFalse);
	//}}AFX_DATA_MAP
}


BEGIN_MESSAGE_MAP(CVisaAttributeExplorer, CDialog)
	//{{AFX_MSG_MAP(CVisaAttributeExplorer)
	ON_CBN_SELCHANGE(IDC_ATTRIBUTE_LIST, OnSelchangeAttributeList)
	ON_BN_CLICKED(IDC_GET_ATTRIBUTE, OnGetAttribute)
	ON_BN_CLICKED(IDC_SET_ATTRIBUTE, OnSetAttribute)
	//}}AFX_MSG_MAP
END_MESSAGE_MAP()


/////////////////////////////////////////////////////////////////////////////
// CVisaAttributeExplorer message handlers

BOOL CVisaAttributeExplorer::OnInitDialog() 
{
	CDialog::OnInitDialog();

	//
	// Load combo box with all attribute names in metadata table.
	//	
	pAttribMetadataTableEntry pScan;
	for (pScan = g_tableVisaAttribMetadata; pScan->m_pszSymbolicName != NULL; ++pScan)
	{
		m_comboAttributes.AddString(pScan->m_pszSymbolicName);
	}
	//
	// Currently, the last LB item will be VI_ATTR_TMO_VALUE -- a useful
	// attribute to start on.
	//
	m_comboAttributes.SetCurSel(m_comboAttributes.GetCount() - 1);
	OnSelchangeAttributeList();
	
	return TRUE;  // return TRUE unless you set the focus to a control
	              // EXCEPTION: OCX Property Pages should return FALSE
}


//// CVisaAttributeExplorer::OnSelchangeAttributeList
//
// Handle selection change in attribute combo box.  Update labels that
// show whether attribute is global / per-session and read-only / writable.
// Update enablement of controls that support viSetAttribute() depending on
// read-only and data type for selected atribute.
//
void CVisaAttributeExplorer::OnSelchangeAttributeList() 
{
	m_strCurrValue = "";
	m_strNewValue = "";
	//
	// Use simple lookup routine to find table element for newly selected
	// attribute.
	//
	int iCurrSel = m_comboAttributes.GetCurSel();
	if (iCurrSel == CB_ERR)
	{
		return;
	}
	CString strCurrSel;
	m_comboAttributes.GetLBText(iCurrSel, strCurrSel);
	m_ptblCurrAttr = FindAttributeTableEntry(strCurrSel);
	//
	// Update labels as necessary and enablement of controls.
	//
	if (m_ptblCurrAttr != NULL)
	{
		if (m_ptblCurrAttr->m_fFlags & VISA_ATTRIB_F_GLOBAL)
		{
			m_lblAttrScope.SetWindowText("all sessions");
		}
		else
		{
			m_lblAttrScope.SetWindowText("this session");
		}
		if (m_ptblCurrAttr->m_fFlags & VISA_ATTRIB_F_READONLY)
		{
			m_lblAttrAccess.SetWindowText("read only");
			m_lblDataType.SetWindowText("");
			m_editNewValue.EnableWindow(FALSE);
			m_btnSetAttribute.EnableWindow(FALSE);
		}
		else
		{
			m_lblAttrAccess.SetWindowText("read/write");
			if (m_ptblCurrAttr->m_fDataType == VisaType_Bool)
			{
				m_lblDataType.SetWindowText("");
				m_editNewValue.EnableWindow(FALSE);
			}
			else
			{
				CString strLabel = VisaAttributeDataType2String(m_ptblCurrAttr->m_fDataType);
				strLabel += ":";
				m_lblDataType.SetWindowText(strLabel);
				m_editNewValue.EnableWindow(TRUE);
			}
			m_btnSetAttribute.EnableWindow(TRUE);
		}
		m_btnTrueValue.SetCheck(0);
		m_btnFalseValue.SetCheck(0);
		if (((m_ptblCurrAttr->m_fFlags & VISA_ATTRIB_F_READONLY) == 0) &&
			(m_ptblCurrAttr->m_fDataType == VisaType_Bool))
		{
			m_lblViBoolean.EnableWindow(TRUE);
			m_btnTrueValue.EnableWindow(TRUE);
			m_btnFalseValue.EnableWindow(TRUE);
		}
		else
		{
			m_lblViBoolean.EnableWindow(FALSE);
			m_btnTrueValue.EnableWindow(FALSE);
			m_btnFalseValue.EnableWindow(FALSE);
		}
	}
}


//// CVisaAttributeExplorer::OnGetAttribute
//
//
//
void CVisaAttributeExplorer::OnGetAttribute()
{
	char szNumBuf[32];
	szNumBuf[0] = '\0';

	switch (m_ptblCurrAttr->m_fDataType)
	{
		case VisaType_Bool:
			ViBoolean bValue;
			if (m_pobjParentDlg->GetVisaAttribute(m_ptblCurrAttr->m_idAttrib, &bValue))
			{
				m_strCurrValue = (bValue == VI_TRUE) ? "VI_TRUE" : "VI_FALSE";
			}
			break;
		case VisaType_Int08:
			ViInt8 i8Value;
			if (m_pobjParentDlg->GetVisaAttribute(m_ptblCurrAttr->m_idAttrib, &i8Value))
			{
				_ltoa((long)i8Value, szNumBuf, 10);
			}
			break;
		case VisaType_UInt08:
			ViUInt8 ui8Value;
			if (m_pobjParentDlg->GetVisaAttribute(m_ptblCurrAttr->m_idAttrib, &ui8Value))
			{
				_ultoa((unsigned long)ui8Value, szNumBuf, 10);
			}
			break;
		case VisaType_Int16:
			ViInt16 i16Value;
			if (m_pobjParentDlg->GetVisaAttribute(m_ptblCurrAttr->m_idAttrib, &i16Value))
			{
				if (m_ptblCurrAttr->m_fFlags & VISA_ATTRIB_F_TRI_STATE)
				{
					switch (i16Value)
					{
						case -1:
							m_strCurrValue = "VI_STATE_UNKNOWN(1)";
							break;
						case 0:
							m_strCurrValue = "VI_STATE_UNASSERTED(0)";
							break;
						case 1:
							m_strCurrValue = "VI_STATE_ASSERTED(1)";
							break;
						default:
							_ltoa((long)i16Value, szNumBuf, 10);
							break;
					}
				}
				else
				{
					if (m_ptblCurrAttr->m_fFlags & VISA_ATTRIB_F_SHOW_IN_HEX)
					{
						_ltoa((long)i16Value, szNumBuf, 16);
					}
					else
					{
						_ltoa((long)i16Value, szNumBuf, 10);
					}
				}
			}
			break;
		case VisaType_UInt16:
			ViUInt16 ui16Value;
			if (m_pobjParentDlg->GetVisaAttribute(m_ptblCurrAttr->m_idAttrib, &ui16Value))
			{
				_ultoa((unsigned long)ui16Value, szNumBuf, 10);
			}
			break;
		case VisaType_Int32:
			ViInt32 i32Value;
			if (m_pobjParentDlg->GetVisaAttribute(m_ptblCurrAttr->m_idAttrib, &i32Value))
			{
				_ltoa((long)i32Value, szNumBuf, 10);
			}
			break;
		case VisaType_UInt32:
			ViUInt32 ui32Value;
			if (m_pobjParentDlg->GetVisaAttribute(m_ptblCurrAttr->m_idAttrib, &ui32Value))
			{
				_ultoa((unsigned long)ui32Value, szNumBuf, 10);
			}
			break;
		case VisaType_Str:
			ViChar szValue[VI_FIND_BUFLEN * 2];
			memset(szValue, 0, sizeof(szValue));
			if (m_pobjParentDlg->GetVisaAttribute(m_ptblCurrAttr->m_idAttrib, szValue))
			{
				m_strCurrValue = szValue;
			}
			break;
	}
	if (szNumBuf[0] != '\0')
	{
		m_strCurrValue = szNumBuf;
		if (m_ptblCurrAttr->m_fFlags & VISA_ATTRIB_F_SHOW_IN_HEX)
		{
			m_strCurrValue += " Hex";
		}
	}
	UpdateData(FALSE);
}


//// CVisaAttributeExplorer::OnSetAttribute
//
//
//
void CVisaAttributeExplorer::OnSetAttribute()
{
	UpdateData();
	if (m_ptblCurrAttr->m_fDataType == VisaType_Bool)
	{
		ViBoolean bValue = (ViBoolean)((m_iFalse == 0) ? VI_FALSE : VI_TRUE);
		m_pobjParentDlg->SetVisaAttribute(m_ptblCurrAttr->m_idAttrib, bValue);
	}
	else	// must be numeric attribute -- no writable ViString attributes
	{
		switch (m_ptblCurrAttr->m_fDataType)
		{
			case VisaType_Int08:
				{
					ViInt8 i8Value = (ViInt8) strtol(m_strNewValue, NULL, 10);
					m_pobjParentDlg->SetVisaAttribute(m_ptblCurrAttr->m_idAttrib, (ViAttrState)i8Value);
				}
				break;
			case VisaType_UInt08:
				{
					ViUInt8 ui8Value = (ViUInt8) strtoul(m_strNewValue, NULL, 10);
					m_pobjParentDlg->SetVisaAttribute(m_ptblCurrAttr->m_idAttrib, (ViAttrState)ui8Value);
				}
				break;
			case VisaType_Int16:
				{
					ViInt16 i16Value = (ViInt16) strtol(m_strNewValue, NULL, 10);
					m_pobjParentDlg->SetVisaAttribute(m_ptblCurrAttr->m_idAttrib, (ViAttrState)i16Value);
				}
				break;
			case VisaType_UInt16:
				{
					ViUInt16 ui16Value = (ViUInt16) strtoul(m_strNewValue, NULL, 10);
					m_pobjParentDlg->SetVisaAttribute(m_ptblCurrAttr->m_idAttrib, (ViAttrState)ui16Value);
				}
				break;
			case VisaType_Int32:
				{
					ViInt32 i32Value = strtol(m_strNewValue, NULL, 10);
					m_pobjParentDlg->SetVisaAttribute(m_ptblCurrAttr->m_idAttrib, (ViAttrState)i32Value);
				}
				break;
			case VisaType_UInt32:
				{
					ViUInt32 ui32Value = strtoul(m_strNewValue, NULL, 10);
					m_pobjParentDlg->SetVisaAttribute(m_ptblCurrAttr->m_idAttrib, (ViAttrState)ui32Value);
				}
				break;
		}
	}	
}


void CVisaAttributeExplorer::OnCancel() 
{
	m_pobjParentDlg->AttributeExplorerClosing();
	DestroyWindow();
}


void CVisaAttributeExplorer::PostNcDestroy() 
{
	CDialog::PostNcDestroy();
	delete this;
}
